package graph;

import java.util.ArrayList;
import java.util.Set;

public interface Tree<V, E extends Graph.Edge<V>> {

    /**
     * Return the tree root
     *
     * @return the tree root
     */
    public V root();

    /**
     * Return all nodes of tree
     *
     * @return all nodes of tree
     */
    public Set<V> nodes();

    /**
     * Return the degree of a given node (outdegree + indegree)
     *
     * @param v node of tree
     * @return the degree of a given node (outdegree + indegree)
     */
    public int degree(V v);

    /**
     * Gives the neighbors (father + children) of a vertex
     *
     * @param v node of tree
     * @return the neighbors of a vertex
     */
    public Set<V> neighbors(V v);

    /**
     * Gives the children of a vertex
     *
     * @param v node of tree
     * @return the children of a vertex
     */
    public Iterable<V> children(V v);

    /**
     * Gives the father of a vertex
     *
     * @param v node of tree
     * @return the father of a vertex
     */
    public V father(V v);

    /**
     * get root shrubs (rooted at treeRoot->children)
     *
     * @return list of shrub
     */
    public ArrayList<Shrub<V, E>> shrubs();

    /**
     * check whether tree is empty or not
     *
     * @return tree is empty or not
     */
    public boolean isEmpty();

    /**
     * get graph that represents for the tree
     *
     * @return graph that represents for the tree
     */
    public Graph<V, E> innerGraph();

}
